#ifndef __DRIVERS_DEVICE_H__
#define __DRIVERS_DEVICE_H__

#define DEVICE_FLAG_INIT          0x01
#define DEVICE_FLAG_ACTIVATED     0x02
#define DEVICE_FLAG_OPEN          0x04
#define DEVICE_FLAG_STANDALONE    0x08
#define DEVICE_FLAG_CLOSE         0x10
#define DEVICE_FLAG_RW            0x20
#define DEVICE_FLAG_RO            0x40
#define DEVICE_FLAG_WO            0x80

#define DEVICE_OFLAG_CLOSE           0x000
#define DEVICE_OFLAG_RDONLY          0x001
#define DEVICE_OFLAG_WRONLY          0x002
#define DEVICE_OFLAG_RDWR            0x003
#define DEVICE_OFLAG_OPEN            0x008

enum device_type {
	DEVICE_TYPE_CHAR,
	DEVICE_TYPE_BLOCK,
	DEVICE_TYPE_NETWORK,
	DEVICE_TYPE_NUKNOW
};

struct device {
	struct object parent;
	const struct device_ops *ops;
	void *private_data;
	uint16_t oflag;
	uint16_t flag;
	enum device_type type;
	unsigned char ref_count;

	/* 设备回调函数 */
    err_t (*rx_indicate)(struct device *dev, size_t size);
    err_t (*tx_complete)(struct device *dev, void *buffer);
};

struct device_ops {
	err_t (*init)    (struct device *dev);
	err_t (*open)    (struct device *dev, uint16_t oflag);
	err_t (*close)   (struct device *dev);
	size_t (*read)  (struct device *dev, const size_t offset, void *buffer, size_t size);
	size_t (*write) (struct device *dev, const size_t offset,  const void *buffer, size_t size);
	err_t  (*control) (struct device *dev, int cmd, void *args);
};

/* 注册一个设备 */
extern err_t device_register(struct device *dev, const char *name, const uint16_t flag);

/* 取消注册一个设备 */
extern err_t device_unregister(struct device *dev);

/* 通过名字查找一个设备 */
extern struct device *device_find(const char *name);

/* 初始化一个设备 */
extern err_t device_init(struct device *dev);

/* 打开一个设备 */
extern err_t device_open(struct device *dev, uint16_t oflag);

/* 关闭一个设备 */
extern err_t device_close(struct device *dev);

/* 控制一个设备 */
extern err_t device_control(struct device *dev, int cmd, void *args);

/* 写一个设备 */
extern size_t device_write(struct device *dev, const size_t offset, const void *user_buffer, const size_t size);

/* 读一个设备 */
extern size_t device_read(struct device *dev, const size_t offset, void *user_buffer, const size_t size);

/* 设置接收回调函数 */
extern err_t device_set_rx_indicate(struct device *dev,
                             err_t (*rx_ind)(struct device *dev,
                             size_t size));

/* 设置发送回调函数 */
extern err_t device_set_tx_complete(struct device *dev,
                                   err_t (*tx_done)(struct device *dev,
                                   void *buffer));

#endif /* __DRIVERS_DEVICE_H__ */
